package com.briup.estore.service.impl;

import com.briup.estore.common.constant.ExceptionMsgEnum;
import com.briup.estore.common.dto.OrderCreateDTO;
import com.briup.estore.common.dto.OrderItemCreateDTO;
import com.briup.estore.common.dto.OrderPaySuccessDTO;
import com.briup.estore.common.dto.OrderSearchDTO;
import com.briup.estore.common.exception.EstoreException;
import com.briup.estore.common.pojo.*;
import com.briup.estore.common.utils.BeanCopyUtils;
import com.briup.estore.common.utils.MakeIDUtils;
import com.briup.estore.common.vo.OrderBookVO;
import com.briup.estore.common.vo.OrderDetailVO;
import com.briup.estore.common.vo.OrderInfoVO;
import com.briup.estore.dao.*;
import com.briup.estore.dao.impl.*;
import com.briup.estore.service.OrderService;

import java.math.BigDecimal;
import java.util.List;
import java.util.stream.Collectors;

/**
 * @Author briup-adam
 * @Date 2023/8/3 下午2:22
 * @Description
 **/

public class OrderServiceImpl implements OrderService {
    private OrderDao orderDao = new OrderDaoImpl();
    private BookDao bookDao = new BookDaoImpl();
    private OrderItemDao orderItemDao = new OrderItemDaoImpl();
    private UserDao userDao=new UserDaoImpl();
    private ShopCarDao shopCarDao=new ShopCarDaoImpl();

    @Override
    public OrderDetailVO getOrderById(String orderId) {
        Order order = orderDao.selectById(orderId);
        User user = userDao.getUserById(order.getUserId());
        List<OrderItem> items = orderItemDao.selectByOrderId(orderId);
        List<OrderBookVO> orderBookVOS = items.stream().map(i -> {
            Book book = bookDao.selectById(i.getBookId());
            OrderBookVO vo = BeanCopyUtils.copyBean(i, OrderBookVO.class);
            vo.setCover(book.getCover());
            vo.setName(book.getName());
            vo.setPrice(book.getPrice());
            return vo;
        }).collect(Collectors.toList());
        OrderDetailVO orderDetailVO = BeanCopyUtils.copyBean(order, OrderDetailVO.class);
        orderDetailVO.setOrderItems(orderBookVOS);
        orderDetailVO.setUsername(user.getUsername());
        return orderDetailVO;
    }

    @Override
    public void closeOrder(String id) {
        Order order = orderDao.selectById(id);
        if (order.getStatus()!=1){
            throw  new EstoreException(ExceptionMsgEnum.ORDER_CAN_NOT_CLOSE);
        }
        orderDao.updateStatusToClose(id);
        List<OrderItem> list = orderItemDao.selectByOrderId(id);
        for (OrderItem item : list) {
            bookDao.updateStoreNumById(item.getNum(),item.getBookId());
        }


    }

    @Override
    public List<OrderInfoVO> getOrders(int userId, OrderSearchDTO orderSearchDTO) {
        List<Order> list = orderDao.selectOrderDetailByUserId(orderSearchDTO.getId(), orderSearchDTO.getStatus(), userId);
        List<OrderInfoVO> vos = list.stream().map(i -> {
            OrderInfoVO infoVO = BeanCopyUtils.copyBean(i, OrderInfoVO.class);
            User user = userDao.getUserById(i.getUserId());
            infoVO.setUsername(user.getUsername());
            List<OrderItem> items = orderItemDao.selectByOrderId(i.getId());
            items.forEach(item -> {
                infoVO.setTotalNum(infoVO.getTotalNum() + item.getNum());
                Book book = bookDao.selectById(item.getBookId());
                infoVO.setTotalPrice(infoVO.getTotalPrice().add(BigDecimal.valueOf(item.getNum()).multiply(BigDecimal.valueOf(book.getPrice()))));
            });
            return infoVO;
        }).collect(Collectors.toList());
        return vos;
    }

    @Override
    public OrderDetailVO createOrder(OrderCreateDTO orderCreateDTO, int userId) {
        String orderId = MakeIDUtils.generateOrderID();
        Order order = BeanCopyUtils.copyBean(orderCreateDTO, Order.class);
        order.setUserId(userId);
        order.setId(orderId);
        orderDao.save(order);
        orderCreateDTO.getShopCarIds().forEach(i->{
            ShopCar shopcar = shopCarDao.findById(i);
            OrderItem item = BeanCopyUtils.copyBean(shopcar, OrderItem.class);
            item.setOrderId(order.getId());
            orderItemDao.save(item);
            shopCarDao.deleteById(i);
            bookDao.updateStoreNumById(Math.negateExact(item.getNum()),item.getBookId());
        });

        return getOrderById(orderId);
    }

    @Override
    public void paySuccess(OrderPaySuccessDTO paySuccessDTO) {
        orderDao.paySuccess(paySuccessDTO.getOrderId(), paySuccessDTO.getPayDate(), paySuccessDTO.getPayWay());
    }

    @Override
    public void completeOrder(String orderId) {
        Order order = orderDao.selectById(orderId);
        if (order.getStatus()!=3)
            throw new EstoreException(ExceptionMsgEnum.ORDER_CAN_NOT_COMPLETE);
        orderDao.completeOrder(orderId);
    }
}
